package com.pj.lib.auraServer.components.DB;

import java.sql.Connection;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.Properties;

import com.pj.lib.auraServer.app.properties.DBProperties;
import com.pj.lib.auraServer.components.DB.tables.TableInterface;
import com.pj.lib.auraServer.exceptions.*;




public abstract class DB {


    protected Connection conn;

    
    
    protected Properties properties;
    protected Properties tableInstances;
    
    public static final String POSTGRESQL_DB = "POSTGRES_SQL";
    public static final String MYSQL_DB = "MYSQL";


    
    public static final String INSTANCE_USER = "USER";
    public static final String INSTANCE_USER_LOCATION = "USER_LOCATION";
    public static final String INSTANCE_AURA_TYPE = "AURA_TYPE";
    public static final String INSTANCE_USER_STATE = "USER_STATE";
    public static final String INSTANCE_USER_STATE_TYPE = "USER_STATE_TYPE";
    
    public DB(DBProperties props) {
    	
    	properties = new Properties();
    	properties.put(DBProperties.KEY_URL, props.URL);
    	properties.put(DBProperties.KEY_PORT, props.PORT);
    	properties.put(DBProperties.KEY_SCHEMA, props.SCHEMA);
    	properties.put(DBProperties.KEY_USER, props.USER);
    	properties.put(DBProperties.KEY_PASS, props.PASS);
    	
	}
    
    public DB(DBProperties props, Properties tableInstances){
    	properties = new Properties();
    	properties.put(DBProperties.KEY_URL, props.URL);
    	properties.put(DBProperties.KEY_PORT, props.PORT);
    	properties.put(DBProperties.KEY_SCHEMA, props.SCHEMA);
    	properties.put(DBProperties.KEY_USER, props.USER);
    	properties.put(DBProperties.KEY_PASS, props.PASS);
    	
    	this.tableInstances = tableInstances;
    }
    
	public abstract void connect() throws ClassNotFoundException, NoSuchDBException, SQLException;
	
    public Boolean isConnected() {
    	try {
	        if(conn == null || conn.isClosed()){
	            return false;
	        } else {
	            return true;
	        }
    	} catch(Exception e) {
    		e.printStackTrace();
    		return false;
    	}
    }
    public Connection getConnection() {
        return conn;
    }
    
    public TableInterface getInstance(String instanceType) {
    	return (TableInterface) tableInstances.get(instanceType);
    }
    
    public void transactionStart() throws SQLException {
    	conn.setAutoCommit(false);
    }
    
    public void transactionCommit() throws SQLException {
    	conn.commit();
    	conn.setAutoCommit(true);
    }
    
    public void transactionRollback() throws SQLException {
    	conn.rollback();
    	conn.setAutoCommit(true);
    }

    public abstract ArrayList<Map<String, Object>> get(String sql, Object[] params) throws AuraServerException, SQLException;
    public abstract ArrayList<Map<String, Object>> get(String sql, List<Object> params) throws AuraServerException, SQLException;
    public abstract ArrayList<Map<String, Object>> get(String sql) throws AuraServerException, SQLException;
    public abstract int update(String sql, Object[] params) throws AuraServerException, SQLException;
    public abstract int update(String sql, List<Object> params) throws AuraServerException, SQLException;
    public abstract int update(String sql) throws AuraServerException, SQLException;
    public abstract void exec(String sql) throws AuraServerException, SQLException;
   
    public abstract void createDB() throws AuraServerException, SQLException;
    
    
    
   

}

